package api

import (
	"awesomeProject/internal/service"
	"awesomeProject/pkg/utils"
	"net/http"
	"strconv"

	"github.com/gin-gonic/gin"
)

type UserController struct {
	userService service.UserService
}

func NewUserController(userService service.UserService) *UserController {
	return &UserController{
		userService: userService,
	}
}

func (uc *UserController) Register(c *gin.Context) {
	var req service.RegisterRequest
	if err := c.ShouldBindJSON(&req); err != nil {
		c.JSON(http.StatusBadRequest, gin.H{"error": "Invalid request format"})
		return
	}
	user, err := uc.userService.Register(c, &req)
	if err != nil {
		utils.HandleError(c, err)
		return
	}
	c.JSON(http.StatusCreated, gin.H{
		"message": "User registered successfully",
		"user":    user,
	})
}

func (uc *UserController) Login(c *gin.Context) {
	var req service.LoginRequest
	if err := c.ShouldBindJSON(&req); err != nil {
		c.JSON(http.StatusBadRequest, gin.H{
			"error": "Invalid request format"})
		return
	}
	token, err := uc.userService.Login(c, &req)
	if err != nil {
		utils.HandleError(c, err)
		return
	}
	c.JSON(http.StatusOK, gin.H{
		"message": "Login successful",
		"token":   token,
		"type":    "Bearer",
	})
}

// RefreshToken 刷新JWT token
func (uc *UserController) RefreshToken(c *gin.Context) {
	// 从请求头获取当前token
	currentToken, exists := c.Get("token")
	if !exists {
		c.JSON(http.StatusUnauthorized, gin.H{
			"error": "Token not found in context",
		})
		return
	}

	newToken, err := uc.userService.RefreshToken(c, currentToken.(string))
	if err != nil {
		utils.HandleError(c, err)
		return
	}

	c.JSON(http.StatusOK, gin.H{
		"message": "Token refreshed successfully",
		"token":   newToken,
		"type":    "Bearer",
	})
}

func (uc *UserController) GetProfile(c *gin.Context) {
	userID := utils.GetUserIDFromContext(c)
	user, err := uc.userService.GetProfile(c, userID)
	if err != nil {
		utils.HandleError(c, err)
		return
	}
	c.JSON(http.StatusOK, gin.H{"user": user})
}

// PUT /api/users/profile
func (uc *UserController) UpdateProfile(c *gin.Context) {
	userID := utils.GetUserIDFromContext(c)
	var req service.UpdateProfileRequest
	if err := c.ShouldBindJSON(&req); err != nil {
		c.JSON(http.StatusBadRequest, gin.H{"error": "Invalid request format"})
		return
	}

	err := uc.userService.UpdateProfile(c, userID, &req)
	if err != nil {
		utils.HandleError(c, err)
		return
	}

	c.JSON(http.StatusOK, gin.H{"message": "Profile updated successfully"})
}

// PUT /api/users/password
func (uc *UserController) ChangePassword(c *gin.Context) {
	userID := utils.GetUserIDFromContext(c)
	var req service.ChangePasswordRequest
	if err := c.ShouldBindJSON(&req); err != nil {
		c.JSON(http.StatusBadRequest, gin.H{"error": "Invalid request format"})
		return
	}

	err := uc.userService.ChangePassword(c, userID, &req)
	if err != nil {
		utils.HandleError(c, err)
		return
	}

	c.JSON(http.StatusOK, gin.H{"message": "Password changed successfully"})
}

// DELETE /api/users/account
func (uc *UserController) DeleteAccount(c *gin.Context) {
	userID := utils.GetUserIDFromContext(c)
	err := uc.userService.DeleteAccount(c, userID)
	if err != nil {
		utils.HandleError(c, err)
		return
	}

	c.JSON(http.StatusOK, gin.H{"message": "Account deleted successfully"})
}

// GET /api/users
func (uc *UserController) ListUsers(c *gin.Context) {
	page, _ := strconv.Atoi(c.DefaultQuery("page", "1"))
	limit, _ := strconv.Atoi(c.DefaultQuery("limit", "10"))

	users, total, err := uc.userService.GetUserList(c, page, limit)
	if err != nil {
		utils.HandleError(c, err)
		return
	}

	c.JSON(http.StatusOK, gin.H{
		"users": users,
		"total": total,
		"page":  page,
		"limit": limit,
	})
}